﻿using System.Collections.Generic;
using UnityEngine;
using UnityEngine.Events;
using UnityEngine.UI;
using System.Collections.Concurrent;

namespace Jinndev {

    [System.Obsolete]
    public class UIBase : MonoBehaviour {

        private ConcurrentQueue<System.Action> actionQueue = new ConcurrentQueue<System.Action>();

        protected void EnqueueAction(System.Action action) {
            actionQueue.Enqueue(action);
        }

        protected void TryInvokeSingleAction() {
            if(actionQueue != null) {
                if (actionQueue.TryDequeue(out System.Action action)) {
                    try {
                        action?.Invoke();
                    }
                    catch (System.Exception e) {
                        Debug.LogException(e);
                    }
                }
            }
        }

        protected void TryInvokeAllActions() {
            if (actionQueue != null) {
                while (actionQueue.TryDequeue(out System.Action action)) {
                    try {
                        action?.Invoke();
                    }
                    catch (System.Exception e) {
                        Debug.LogException(e);
                    }
                }
            }
        }

        public void Invoke(UnityAction action) {
            if (action != null) {
                action.Invoke();
            }
        }

        public void Invoke<T0>(UnityAction<T0> action, T0 arg0) {
            if (action != null) {
                action.Invoke(arg0);
            }
        }

        public void Invoke<T0, T1>(UnityAction<T0, T1> action, T0 arg0, T1 arg1) {
            if (action != null) {
                action.Invoke(arg0, arg1);
            }
        }

        public void Invoke<T0, T1, T2>(UnityAction<T0, T1, T2> action, T0 arg0, T1 arg1, T2 arg2) {
            if (action != null) {
                action.Invoke(arg0, arg1, arg2);
            }
        }

        #region CommonUtil
        public Transform GetTransform(string path) {
            return CommonUtil.GetTransform(transform, path);
        }

        public Transform GetTransform(Object parent, string path) {
            return CommonUtil.GetTransform(parent, path);
        }

        public GameObject GetGameObject(string path) {
            return CommonUtil.GetGameObject(transform, path);
        }

        public GameObject GetGameObject(Object parent, string path) {
            return CommonUtil.GetGameObject(parent, path);
        }

        public T GetComponent<T>(string path) where T : Component {
            return CommonUtil.GetComponent<T>(transform, path);
        }

        public T GetComponent<T>(Object parent, string path) where T : Component {
            return CommonUtil.GetComponent<T>(parent, path);
        }

        public GameObject Instantiate(string prefabPath, string path) {
            return CommonUtil.Instantiate(prefabPath, CommonUtil.GetTransform(transform, path));
        }

        public GameObject Instantiate(string prefabPath, Object parent, string path) {
            return CommonUtil.Instantiate(prefabPath, CommonUtil.GetTransform(parent, path));
        }

        public T Instantiate<T>(string prefabPath, string path) where T : Component {
            return CommonUtil.Instantiate<T>(prefabPath, CommonUtil.GetTransform(transform, path));
        }

        public T Instantiate<T>(string prefabPath, Object parent, string path) where T : Component {
            return CommonUtil.Instantiate<T>(prefabPath, CommonUtil.GetTransform(parent, path));
        }

        public void Destroy() {
            Destroy(gameObject);
        }

        public void DestroyChild(string path) {
            CommonUtil.DestroyChild(transform, path);
        }

        public void DestroyChild(Object parent, string path) {
            CommonUtil.DestroyChild(parent, path);
        }

        public void DestroyChildImmediate(string path) {
            CommonUtil.DestroyChildImmediate(transform, path);
        }

        public void DestroyChildImmediate(Object parent, string path) {
            CommonUtil.DestroyChildImmediate(parent, path);
        }

        public void DestroyChildren(string path) {
            CommonUtil.DestroyChildren(transform, path);
        }

        public void DestroyChildren(Object parent, string path) {
            CommonUtil.DestroyChildren(parent, path);
        }

        public void DestroyChildrenImmediate(string path) {
            CommonUtil.DestroyChildrenImmediate(transform, path);
        }

        public void DestroyChildrenImmediate(Object parent, string path) {
            CommonUtil.DestroyChildrenImmediate(parent, path);
        }

        public void SetActive(string path, bool active) {
            CommonUtil.SetActive(transform, path, active);
        }

        public void SetActive(Object parent, string path, bool active) {
            CommonUtil.SetActive(parent, path, active);
        }

        public bool ToggleActive(string path) {
            return CommonUtil.ToggleActive(transform, path);
        }

        public bool ToggleActive(Object parent, string path) {
            return CommonUtil.ToggleActive(parent, path);
        }
        #endregion

        public void ForceLayout(string path) {
            UIUtil.ForceLayout(transform, path);
        }

        public void ForceLayout(Object parent, string path) {
            UIUtil.ForceLayout(parent, path);
        }

        public void SetImage(string path, Sprite sprite) {
            UIUtil.SetImage(transform, path, sprite);
        }

        public void SetImage(Object parent, string path, Sprite sprite) {
            UIUtil.SetImage(parent, path, sprite);
        }

        public void SetRawImage(string path, Texture2D texture) {
            UIUtil.SetRawImage(transform, path, texture);
        }

        public void SetRawImage(Object parent, string path, Texture2D texture) {
            UIUtil.SetRawImage(parent, path, texture);
        }

        public void SetText(string path, string text) {
            UIUtil.SetText(transform, path, text);
        }

        public void SetText(Object parent, string path, string text) {
            UIUtil.SetText(parent, path, text);
        }

        public void SetTextAndColor(string path, string text, Color color) {
            UIUtil.SetTextAndColor(transform, path, text, color);
        }

        public void SetTextAndColor(Object parent, string path, string text, Color color) {
            UIUtil.SetTextAndColor(parent, path, text, color);
        }

        public void SetInputText(string path, object text) {
            UIUtil.SetInputText(transform, path, text);
        }

        public void SetInputText(Object parent, string path, object text) {
            UIUtil.SetInputText(parent, path, text);
        }

        public string GetInputText(string path, string defaultValue = null) {
            return UIUtil.GetInputText(transform, path, defaultValue);
        }

        public string GetInputText(Object parent, string path, string defaultValue = null) {
            return UIUtil.GetInputText(parent, path, defaultValue);
        }

        public void AddInputChange(string path, UnityAction<string> action) {
            UIUtil.AddInputChange(transform, path, action);
        }

        public void AddInputChange(Object parent, string path, UnityAction<string> action) {
            UIUtil.AddInputChange(parent, path, action);
        }

        public void SetDropdownOptions(string path, List<Dropdown.OptionData> options) {
            UIUtil.SetDropdownOptions(transform, path, options);
        }

        public void SetDropdownOptions(Object parent, string path, List<Dropdown.OptionData> options) {
            UIUtil.SetDropdownOptions(parent, path, options);
        }

        public void SetDropdownValue(string path, int value) {
            UIUtil.SetDropdownValue(transform, path, value);
        }

        public void SetDropdownValue(Object parent, string path, int value) {
            UIUtil.SetDropdownValue(parent, path, value);
        }

        public int GetDropdownValue(string path) {
            return UIUtil.GetDropdownValue(transform, path);
        }

        public int GetDropdownValue(Object parent, string path) {
            return UIUtil.GetDropdownValue(parent, path);
        }

        public void AddButtonClick(string path, UnityAction action) {
            UIUtil.AddButtonClick(transform, path, action);
        }

        public void AddButtonClick(Object parent, string path, UnityAction action) {
            UIUtil.AddButtonClick(parent, path, action);
        }

        public void AddToggleChange(string path, UnityAction<bool> action) {
            UIUtil.AddToggleChange(transform, path, action);
        }

        public void AddToggleChange(Object parent, string path, UnityAction<bool> action) {
            UIUtil.AddToggleChange(parent, path, action);
        }

        public void SetToggleValue(string path, bool isOn) {
            UIUtil.SetToggleValue(transform, path, isOn);
        }

        public void SetToggleValue(Object parent, string path, bool isOn) {
            UIUtil.SetToggleValue(parent, path, isOn);
        }

        public bool GetToggleValue(string path) {
            return UIUtil.GetToggleValue(transform, path);
        }

        public bool GetToggleValue(Object parent, string path) {
            return UIUtil.GetToggleValue(parent, path);
        }

        public void SetButtonInteractive(string path, bool interactable) {
            UIUtil.SetButtonInteractable(transform, path, interactable);
        }

        public void SetButtonInteractive(Object parent, string path, bool interactable) {
            UIUtil.SetButtonInteractable(parent, path, interactable);
        }

    }
}
